pub const GOOD_WEIGHT: f32 = 1.0;
pub const BAD_WEIGHT: f32 = 2.0;

#[derive(Debug, PartialEq)]
pub enum Niceness {
    Nice(u32),
    Naughty,
}

pub struct Kid {
    pub name: String,
    pub niceness: Niceness,
}

impl Kid {
    pub fn parse_row(csv_row: &str) -> Result<Kid, &'static str> {
        // 🎁 Transform the CSV row into a Kid struct for Santa's list!
        // 🎅 Expected CSV: "Name,GoodDeeds,BadDeeds"
        //    Example: "Alice,3,1" -> name: "Alice", good_deeds: 3, bad_deeds: 1

        // 🎁 Your code here! 🎁
        let mut meet_err = false;
        let mut err_msg = String::new();
        if csv_row.is_empty() {
            meet_err = true;
            err_msg = String::from("Input is empty!");
        }
        let data: Vec<&str> = csv_row.split(',').collect();

        let mut name = "";
        let mut good_deeds = 0;
        let mut bad_deeds = 0;
        if data.len() == 3 {
            name = data[0];
            if let Ok(u) = data[1].parse::<u32>() {
                good_deeds = u;
            } else {
                return Err("good_deeds parse error");
            }
            if let Ok(u) = data[2].parse::<u32>() {
                bad_deeds = u;
            } else {
                return Err("bad_deeds parse error");
            }
        } else {
            return Err("input format error");
        }
        Ok(Self::new(name.to_string(), good_deeds, bad_deeds))

        /*
        let mut fields = csv_row.split(",");
        let name = fields.next().ok_or("missing field")?.to_string();
        let good_deeds: u32 = fields.next().ok_or("missing field")?.parse().map_err(|_| "Invalid good deeds")?;
        let bad_deeds: u32 = fields.next().ok_or("missing field")?.parse().map_err(|_| "Invalid bad deeds")?;
        Ok(Self::new(name, good_deeds, bad_deeds))
        */

        /*
        let mut entries = csv_row.split(',');
        let [Some(name), Some(good_deeds), Some(bad_deeds), None] = std::array::from_fn(|_| entries.next()) else {
            return Err("expected 3 columns");
        };
        Ok(Self::new(
            name.to_string(),
            good_deeds.parse().map_err(|_| "good deeds is not a number")?,
            bad_deeds.parse().map_err(|_|"bad deeds is not a number")?
        ))
        */
    }

    pub fn new(name: String, good_deeds: u32, bad_deeds: u32) -> Self {
        let niceness = if Self::is_nice(good_deeds, bad_deeds) {
            Niceness::Nice(good_deeds)
        } else {
            Niceness::Naughty
        };

        Self { name, niceness }
    }

    pub fn is_nice(good_deeds: u32, bad_deeds: u32) -> bool {
        if good_deeds == 0 && bad_deeds == 0 {
            return false;
        }

        let good_deeds = good_deeds as f32 * GOOD_WEIGHT;
        let bad_deeds = bad_deeds as f32 * BAD_WEIGHT;

        let ratio = good_deeds / (good_deeds + bad_deeds);

        ratio >= 0.75
    }
}
